home *** CD-ROM | disk | FTP | other *** search
/ AOL File Library: 2,801 to 2,900 / aol-file-protocol-4400-2801-to-2900.zip / AOLDLs / C++ Files Library / Graphic Gems I, II & III (C_C++) / Graphics Gems C Code.sea / GemsIII / 3d.c next >
Text File  |  1992-06-16  |  4KB  |  98 lines

  1. /* rolling-ball-gems3.c */
  2. /* 
  3.  * Take a 3D graphics object "obj" and the incremental mouse
  4.  * motion data "(dx,dy,state)" and rotate the object
  5.  * using the rolling ball algorithm.  A generic interactive
  6.  * graphics interface is assumed that maps onto common protocols 
  7.  * such as Xlib in an obvious way.
  8.  *
  9.  * It is assumed that an object "obj" of type "Polyhedron" has
  10.  * already been drawn once on the display, and that it carries
  11.  * a 4x4 frame matrix "obj->frame[i][j]" specifying the position
  12.  * and orientation at which it is to be drawn.
  13.  *
  14.  * Make3DRot  is assumed to construct a 4x4 rotation matrix from
  15.  * the angle and axis parameters as shown in the text and in
  16.  * GGI "Rotation Tools," by M. Pique, p.466.
  17.  *
  18.  * Make3DTranslation  is assumed to store an (x,y,z) position in a 4x4 
  19.  * matrix in such a way that it can be extracted by  Tx = obj->frame[3][0]; .
  20.  *
  21.  * CombineMatrices3D  performs a left to right matrix multiplication,
  22.  * leaving the result in the location specified by the last argument.
  23.  *
  24.  * CopyMatrix3D  copies a matrix into another.
  25.  *
  26.  * Entry:  display       - generic graphics device specification.
  27.  *         obj           - the object (typically a wire frame) to be rotated.
  28.  *         dx,dy         - the distance the mouse moved in screen coordinates
  29.  *                         since the previous event was processed.
  30.  *         state         - state of the mouse such as button presses.
  31.  *
  32.  * Exit: Object "obj" erased, rotated, and redrawn.
  33.  */
  34.  
  35. #include <math.h>
  36. #include "defs.h"
  37.  
  38. ModifyObject(display, obj, dx, dy, state)
  39.      Display *display;
  40.      Polyhedron *obj;
  41.      int dx, dy, state;
  42. {double Tx, Ty, Tz, n[3], dr, denom, cos_theta, sin_theta;
  43.  double Matrix3D[4][4], TmpMat[4][4], TransToOrigin[4][4], Rmat[4][4];
  44.  static double Radius=100.0;
  45.  
  46.  /* Example of interactive method: apply rolling ball to
  47.   *  object's orientation as long as mouse Button1 is 
  48.   *  held down.
  49.   */
  50.  if (state == Button1)
  51.    {
  52.      /* Obtain current object position from its frame. */
  53.      Tx = obj->frame[3][0];
  54.      Ty = obj->frame[3][1];
  55.      Tz = obj->frame[3][2];
  56.  
  57.      /* Compute the rolling ball axis and angle from the incremental mouse 
  58.       * displacements (dx,dy) and compute corresponding rotation matrix RMat.
  59.       * See text for full form of Rmat returned by Make3DRot.
  60.       * NOTE: For window systems using a left-handed screen 
  61.       * coordinate system, the formula (-dy,dx,0) given
  62.       * in the text for the rotation axis direction must
  63.       * be changed to (+dy,dx,0) to give the desired effect!
  64.       * We explicitly use this coordinate system in the example
  65.       * code because so many systems possess this reversal.
  66.       */
  67.      dr = sqrt((double)(dx*dx + dy*dy));
  68.      denom = sqrt(Radius*Radius + dr*dr);
  69.      cos_theta = Radius/denom;
  70.      sin_theta = dr/denom;
  71.      n[0] = (double)(dy)/dr;   /* Change sign for right-handed coord system. */
  72.      n[1] = (double)(dx)/dr;
  73.      n[2] = 0.0;
  74.      Make3DRot(cos_theta, sin_theta, n, Rmat);
  75.  
  76.      /* Translate current object frame to origin. */
  77.      Make3DTranslation(-Tx, -Ty, -Tz, TransToOrigin);
  78.      CombineMatrices3D(TransToOrigin, obj->frame, Matrix3D);
  79.  
  80.      /* Rotate about origin. */
  81.      CombineMatrices3D(Rmat, Matrix3D, TmpMat);
  82.      
  83.      /* Translate rotated temporary frame back to original object position. */
  84.      Make3DTranslation(Tx, Ty, Tz, TransToOrigin);
  85.      CombineMatrices3D(TransToOrigin, TmpMat, Matrix3D);
  86.  
  87.      /* Erase current object. */
  88.      SetFunction(display, ERASE);
  89.      DrawObject(display, obj);
  90.  
  91.      /* Install new frame in object, draw rotated object. */
  92.      CopyMatrix3D(Matrix3D, obj->frame);
  93.      SetFunction(display, DRAW);
  94.      DrawObject(display, obj);
  95.  
  96.    }}
  97.  
  98.